# -*- mode: org; -*-
#+TITLE: Crontab Guide
#+AUTHOR: Zelphir Kaltstahl
#+EMAIL: zelphirkaltstahl@posteo.de
#+STARTUP: content indent align inlineimages hideblocks entitiesplain nologdone nologreschedule nologredeadline nologrefile
#+TODO: TODO WIP DEPRECATED | DONE
#+DATE: [2022-01-09 Sun]
#+KEYWORDS: server crontab cronjob devops logging schedule
#+LANGUAGE: English
#+PRIORITIES: A E E
#+EXCLUDE_TAGS: noexport
#+OPTIONS: ^:{}
#+OPTIONS: H:10
#+OPTIONS: toc:2
#+OPTIONS: tags:nil
#+OPTIONS: tasks:t
#+OPTIONS: H:6
#+OPTIONS: p:nil
#+OPTIONS: pri:nil
#+OPTIONS: prop:nil
#+OPTIONS: todo:t
#+OPTIONS: stat:nil
#+OPTIONS: |:t
#+OPTIONS: inline:nil
#+OPTIONS: date:t


* Syntax

The schedule specification syntax is:

#+begin_src crontab
minute hour day month weekday
#+end_src

* Logs

** General log files

General logs of crontab can be viewed using the following command:

#+begin_src shell
grep CRON /var/log/syslog
#+end_src

This probably requires to have =rsyslog= installed.

If no logs show up, check the file =/etc/rsyslog.d/50-default.conf= for a commented out line like =#cron.*= and uncomment it. Then restart =rsyslog= using ~service rsyslog restart~.

** Logging each job

*** Variant 1 - redirect stderr and output to log file

#+begin_src crontab
0 13 * * * call_to_script >> /home/log/myscript.log 2>&1
#+end_src

*** Variant 2 - redirect stderr and stdout to separate files

#+begin_src crontab
42 17 * * * command >>stdout.log 2>>stderr.log
#+end_src

*** Variant 3 - redirect and display using tee

#+begin_src crontab
0 13 * * * call_to_script 2>&1 | tee --append log_file 2>&1
#+end_src

This has the advantage, that the cronjob is observable, when run manually.

*** Variant 4 - redirect and display without depending on tee in docker containers

#+begin_src crontab
0 9 * * * command > /proc/1/fd/1 2>&1
#+end_src

The =/proc/1/fd/1= is explained as follows: =/proc/PID/fd/1= where =/proc= is a conventional location, then follows the PID of the process whose file descriptors will be used, then =/fd=, which stands for "file descriptors" and then =/1= for stdout or =/2= for stderr.

Docker always uses the stdout from process with PID 1 as the docker log stream, so redirecting output to =/proc/1/fd/1= will make the output visible in ~docker logs ...~ output.

*** Variant 5 - redirect and display without depending on tee

#+begin_src crontab
0 9 * * * command > /proc/$(cat /var/run/crond.pid)/fd/1 2>&1
#+end_src

The =/proc/1/fd/1= is explained as follows: =/proc/PID/fd/1= where =/proc= is a conventional location, then follows the PID of the process whose file descriptors will be used, then =/fd=, which stands for "file descriptors" and then =/1= for stdout or =/2= for stderr.

~$(cat /var/run/crond.pid)~ will find the PID of the running cron process.
